﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Globalization;
using System.Threading;

namespace ShoppingCenter
{
    class Program
    {
        static private StringBuilder sb = new StringBuilder();
        static private Dictionary<int,Product> Products = new Dictionary<int, Product>();
        static private Dictionary<string, List<int>> Names = new Dictionary<string,List<int>>();
        static private Dictionary<string, List<int>> Producers= new Dictionary<string,List<int>>();
        static private SortedList<float, List<int>> Prices = new SortedList<float,List<int>>();
        static void Main(string[] args)
        {
            Thread.CurrentThread.CurrentCulture = CultureInfo.InvariantCulture;
            int N = int.Parse(Console.ReadLine());
            for (int i = 0; i < N; i++)
            {
                string inputLine = Console.ReadLine();
                //if (inputLine == "FindProductsByPriceRange 3.0;7")
                //{
                //    int a = 0;
                //}
                string command = inputLine.Substring(0, inputLine.IndexOf(' '));
                string[] parameters = inputLine.Substring(inputLine.IndexOf(' ') + 1).Split(new char[] { ';' }, StringSplitOptions.RemoveEmptyEntries);
                switch (command) 
                {
                    case "AddProduct":
                        {
                            addProduct(i, parameters[0], parameters[1], parameters[2]);   
                        }
                        break;
                    case "DeleteProducts":
                        {
                            if (parameters.Length == 1 )
                            {
                                delProducts(parameters[0]);
                            }
                            else
                            {
                                delProducts(parameters[0], parameters[1]);
                            }
                        }
                        break;
                    case "FindProductsByName":
                        {
                            findProductsByName(parameters[0]);
                        }
                        break;
                    case "FindProductsByProducer":
                        {
                            findProductsByProducer(parameters[0]);
                        }
                        break;
                    case "FindProductsByPriceRange":
                        {
                            findProductsByPriceRange(float.Parse(parameters[0]), float.Parse(parameters[1]));
                        }
                        break;
                    default:
                        break;
                }
            }
            Console.WriteLine(sb);
        }
        static private void addProduct(int i, string Name, string Price, string Producer)
        {
            float floatPrice = float.Parse(Price);
            Product prod = new Product(Name, Producer, floatPrice);
            sb.AppendLine("Product added");
            Products.Add(i,prod);
            if (Prices.ContainsKey(floatPrice))
            {
                Prices[floatPrice].Add(i);
            }
            else
            {
                Prices.Add(floatPrice, new List<int> { i });
            }
            
            if (Names.ContainsKey(Name))
            {
                Names[Name].Add(i);
            }
            else
            {
                Names.Add(Name, new List<int> { i });
            }
            if (Producers.ContainsKey(Producer))
            {
                Producers[Producer].Add(i);
            }
            else
            {
                Producers.Add(Producer, new List<int> { i });
            }
        }
        static private void delProducts(string Name, string Producer)
        {
            if (Producers.ContainsKey(Producer) && Producers[Producer].Count >0)
            {
                List<int> idsToDelete = new List<int>();
                foreach(var id in Producers[Producer])
                {
                    if (Products[id].Name == Name)
                    {
                        idsToDelete.Add(id);
                    }
                }
                if (idsToDelete.Count >0 )
                {
                    sb.Append(idsToDelete.Count);
                    sb.AppendLine(" products deleted");
                    Deleteproducts(idsToDelete);                    
                }
                else
                {
                    sb.AppendLine("No products found");
                }
            }
            else
            {
                sb.AppendLine("No products found");
            }
            
        }
        static private void delProducts(string Producer)
        {
            if (Producers.ContainsKey(Producer) && Producers[Producer].Count > 0)
            {
                List<int> idsToDelete = new List<int>();
                foreach (var id in Producers[Producer])
                {
                    idsToDelete.Add(id);
                }
                sb.Append(idsToDelete.Count);
                sb.AppendLine(" products deleted");
                Deleteproducts(idsToDelete);
                Producers.Remove(Producer);
            }
            else
            {
                sb.AppendLine("No products found");
            }
        }

        private static void Deleteproducts(List<int> idsToDelete)
        {
            foreach (var id in idsToDelete)
            {
                string Name = Products[id].Name,
                    Producer = Products[id].Producer;
                float Price = Products[id].Price;
                Products.Remove(id);
                Names[Name].Remove(id);
                Producers[Producer].Remove(id);
                Prices[Price].Remove(id);
            }
            
        }
        static private void findProductsByProducer(string Producer)
        {
            if (Producers.ContainsKey(Producer))
            {
                List<string> result = new List<string>();
                foreach (var id in Producers[Producer])
                {
                    result.Add("{" + Products[id].Name + ";" + Products[id].Producer + ";" + Products[id].Price.ToString("F2", CultureInfo.InvariantCulture) + "}");
                }
                printList(result);
            }
            else
            {
                sb.AppendLine("No products found");
            }
        }
        static private void printList(List<string> result)
        {
            if (result.Count>0)
            {
                result.Sort();
                for (int i = 0; i < result.Count; i++)
                {
                    sb.AppendLine(result[i]);
                }    
            }
            else
            {
                sb.AppendLine("No products found");
            }
        }
        static private void findProductsByPriceRange(float StartPrice, float EndPrice)
        {
            if (Prices.Keys.Count==0)
            {
                sb.AppendLine("No products found");
                return;
            }
            int left = 0,
                right = Prices.Count - 1,
                index = right / 2;
            while (left <= right)//binary search
            {
                index = (right + left) / 2;
                if (StartPrice < Prices.Keys[index])
                {
                    right = index - 1;
                }
                else
                {
                    left = index + 1;
                }
            }
            if (Prices.Keys[index] < StartPrice)
            {
                index++;
            }
            List<string> result = new List<string>();
            while (index < Prices.Keys.Count && Prices.Keys[index] <= EndPrice)
            {
                //int id = Prices.Values[index];
                foreach (var id in Prices[Prices.Keys[index]])
                {
                    result.Add("{" + Products[id].Name + ";" + Products[id].Producer + ";" + Products[id].Price.ToString("F2", CultureInfo.InvariantCulture) + "}");
                }
                index++;
            }
            if (result.Count > 0)
            {
                printList(result);
            }
            else
            {
                sb.AppendLine("No products found");
            }

        }
        static private void findProductsByName(string Name)
        {
            if (Names.ContainsKey(Name))
            {
                List<string> result = new List<string>();
                foreach (var id in Names[Name])
                {
                    result.Add("{" + Products[id].Name + ";" + Products[id].Producer + ";" + Products[id].Price.ToString("F2", CultureInfo.InvariantCulture) + "}");
                }
                printList(result);
            }
            else
            {
                sb.AppendLine("No products found");
            }
        }
    }
    class Product 
    {
        public string Name { get; set; }
        public string Producer { get; set; }
        public float Price { get; set; }
        public Product(string Name, string Producer, float Price)
        {
            this.Name = Name;
            this.Producer = Producer; 
            this.Price = Price;
        }
    }

}
